package com.ala4.oxcafe.serializer.attachment;

import com.ala4.oxcafe.annotation.AttachmentsUrl;
import com.ala4.oxcafe.common.utils.OssClientUtil;
import com.ala4.oxcafe.common.utils.object.ObjectUtil;
import com.ala4.oxcafe.core.entity.AttachmentEntity;
import com.ala4.oxcafe.properties.FileProperties;
import com.aliyun.oss.dto.OSSUrlDTO;
import com.fasterxml.jackson.core.JsonGenerator;
import com.fasterxml.jackson.databind.BeanProperty;
import com.fasterxml.jackson.databind.JsonSerializer;
import com.fasterxml.jackson.databind.SerializerProvider;
import com.fasterxml.jackson.databind.ser.ContextualSerializer;
import org.springframework.stereotype.Component;

import java.io.IOException;
import java.util.Base64;
import java.util.List;
import java.util.stream.Collectors;
import java.util.stream.Stream;

/**
 * 解析附件URL转换器
 *
 * @author PING
 * @date 2025/8/16 21:39
 */
@Component
public class FileKeyListSerializer extends JsonSerializer<String> implements ContextualSerializer {

    private final FileProperties fileProperties;

    public FileKeyListSerializer(FileProperties fileProperties) {
        this.fileProperties = fileProperties;
    }

    @Override
    public void serialize(String valueObj, JsonGenerator gen, SerializerProvider provider)
            throws IOException {
        String value = String.valueOf(valueObj);
        if (value == null || value.trim().isEmpty()) {
            gen.writeStartArray();
            gen.writeEndArray();
            return;
        }

        List<AttachmentEntity> fileInfos = Stream.of(value.split(","))
                .map(String::trim)
                .filter(key -> !key.isEmpty())
                .map(key -> {
                    return new AttachmentEntity(key, resolveUrl(key));
                })
                .collect(Collectors.toList());

        gen.writeObject(fileInfos);
    }

    /**
     * 从fileKey解析获取完整的url
     *
     * @param fileKey 文件key
     * @return
     */
    private String resolveUrl(String fileKey) {
        String filePath = new String(Base64.getDecoder().decode(fileKey));
        if (filePath.contains("/OSS")) {
            OSSUrlDTO ossUrlDTO = OssClientUtil.policyUrl(filePath);
            return ossUrlDTO.getFileUrl();
        } else if (filePath.contains("/LOCAL")) {
            return fileProperties.getStaticHostPath() + filePath;
        }
        return filePath;
    }

    @Override
    public JsonSerializer<?> createContextual(SerializerProvider prov,
                                              BeanProperty property) {
        if (property != null) {
            AttachmentsUrl attachmentsUrl = property.getAnnotation(AttachmentsUrl.class);
            if (ObjectUtil.isNotNull(attachmentsUrl)) {
                return new FileKeyListSerializer(this.fileProperties);
            }
        }
        return this;
    }
}
